﻿using EndpointManagement;
using IM.Easy.Core.AppContext;
using IM.Easy.Core.Utils;
using IM.Easy.CoreServices.IServices;
using IM.Easy.Infrastructure.Constants;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.Filters;
using Microsoft.Extensions.Hosting;

namespace IM.Easy.Api.Filters
{
    public class DemoFilter : ActionFilterAttribute
    {
        private readonly IParamsService _paramsService;
        private readonly IHostEnvironment _hostEnvironment;

        // 如果是演示模式，禁止 POST、PUT、DELETE 等修改行为
        private readonly List<string> denyAction = ["put", "del", "add", "create", "update", "delete", "insert", "upload"];

        public DemoFilter(IParamsService paramsService, IHostEnvironment hostEnvironment)
        {
            _paramsService = paramsService;
            _hostEnvironment = hostEnvironment;
        }

        public override void OnActionExecuting(ActionExecutingContext context)
        {
            var isDemo = _paramsService.GetValue<bool>(ParamsConstant.IsDemo);
            if (isDemo)
            {
                // 获取路由信息
                var routePattern = context.ActionDescriptor?.AttributeRouteInfo?.Template;
                // 获取当前请求路径和方法
                var httpMethod = context.HttpContext.Request.Method;
                var api = EndPointManager.Get($"{routePattern}:{httpMethod}") ?? new Entity.System.ApiPermissions();

                var disable = _hostEnvironment.IsProduction() && (Disable(api.PermissionKey) || IsDelOperate(httpMethod)) && !ImApp.User.IsSuperAdmin;
                var msg = $"演示模式，禁止操作，若有需要请联系开发人员";
                if (disable)
                    ExceptionUtils.ThrowBusinessException(msg);

            }
        }

        public bool Disable(string permissionKey)
        {
            if (string.IsNullOrEmpty(permissionKey)) return false;
            return denyAction.Any(filter => permissionKey.Contains(filter, StringComparison.OrdinalIgnoreCase));
        }

        public bool IsDelOperate(string method)
        {
            return method == HttpMethod.Delete.Method;
        }
    }

}
